package br.ufrj.ppgi.infovis.mtgraph;

import org.mt4j.components.MTComponent;
import org.mt4j.components.visibleComponents.shapes.MTRectangle;
import org.mt4j.components.visibleComponents.shapes.MTRoundRectangle;
import org.mt4j.components.visibleComponents.widgets.MTClipRectangle;
import org.mt4j.components.visibleComponents.widgets.MTClipRoundRect;
import org.mt4j.input.inputProcessors.IGestureEventListener;
import org.mt4j.input.inputProcessors.MTGestureEvent;
import org.mt4j.input.inputProcessors.componentProcessors.dragProcessor.DragEvent;
import org.mt4j.input.inputProcessors.componentProcessors.dragProcessor.DragProcessor;
import org.mt4j.input.inputProcessors.componentProcessors.rotate3DProcessor.Rotate3DProcessor;
import org.mt4j.input.inputProcessors.componentProcessors.rotateProcessor.RotateEvent;
import org.mt4j.input.inputProcessors.componentProcessors.rotateProcessor.RotateProcessor;
import org.mt4j.input.inputProcessors.componentProcessors.scaleProcessor.ScaleEvent;
import org.mt4j.input.inputProcessors.componentProcessors.scaleProcessor.ScaleProcessor;

import processing.core.PApplet;

public class GraphArea extends MTClipRoundRect {
	
	private float scaleFactor = 1f;
	
	public GraphArea(PApplet app, float x, float y, float w, float h) {
		this(app, x, y, 0, w, h);
		
        this.removeAllGestureEventListeners(DragProcessor.class);
        this.removeAllGestureEventListeners(RotateProcessor.class);
        this.removeAllGestureEventListeners(Rotate3DProcessor.class);
        this.removeAllGestureEventListeners(ScaleProcessor.class);
		
		setListeners();
		this.setNoFill(true);
		//this.setNoStroke(true);
		
		
		
	}

	private GraphArea(PApplet applet, float x, float y, float z, float width,
			float height) {
		super(applet, x, y, z, width, height, 25, 25);
	}
	
	private void setListeners() {
		setScaleListener();
		setDragListener();
		setRotateListener();
	}
	
	
	private void setScaleListener() {
        this.addGestureListener(ScaleProcessor.class, 
        		new IGestureEventListener () {
        	public boolean processGestureEvent(MTGestureEvent ge) {
        		MTClipRoundRect rect = (MTClipRoundRect) ge.getTarget();
        		MTComponent[] children = rect.getChildren();

        		ScaleEvent se = (ScaleEvent) ge;
        		scaleFactor *= se.getScaleFactorX();
        //		System.out.println(scaleFactor);

        		System.out.println(children.length);
        		for (MTComponent child : children) {
        			ScaleEvent sc = new ScaleEvent(se.getSource(),se.getId(), 
        					child, se.getFirstCursor(), se.getSecondCursor(), 
        					se.getScaleFactorX(), 
        					se.getScaleFactorY(), se.getScaleFactorY(), se.getScalingPoint());
        			child.processGestureEvent(sc);
        			//System.out.println(child.getClass());
        			//child.scaleGlobal(se.getScaleFactorX(), se.getScaleFactorY(), 
        			//		se.getScaleFactorZ(),se.getScalingPoint());
        			
        		}
        		return false;
        	}}
        		);
	}

	private void setRotateListener() {

		this.addGestureListener(RotateProcessor.class, 
				new IGestureEventListener () {
			public boolean processGestureEvent(MTGestureEvent ge) {
				MTClipRoundRect rect = (MTClipRoundRect) ge.getTarget();
				MTComponent[] children = rect.getChildren();

				RotateEvent re = (RotateEvent) ge;

				for (MTComponent child : children) {
					RotateEvent rc = 
							new RotateEvent(re.getSource(), re.getId(),
									child, re.getFirstCursor(), re.getSecondCursor(), 
									re.getTranslationVector(), re.getRotationPoint(), 
									re.getRotationDegrees());
					child.processGestureEvent(rc);
					//child.rotateZGlobal(re.getRotationPoint(), re.getRotationDegrees());
				}
				return false;
			}}
				);

	}
	
	private void setDragListener() {
	       this.addGestureListener(DragProcessor.class, 
	        		new IGestureEventListener () {
	        	public boolean processGestureEvent(MTGestureEvent ge) {
	        		MTClipRoundRect rect = (MTClipRoundRect) ge.getTarget();
	        		MTComponent[] children =rect.getChildren();

	        		DragEvent de = (DragEvent) ge;
	        		
	        		for (MTComponent child : children) {
	        			MTGestureEvent gc = new DragEvent(ge.getSource(), ge.getId(),
	        					child, de.getDragCursor(), de.getFrom(), de.getTo());
	        			child.processGestureEvent(gc);
	        		}
	        		return false;
	        	}}
	        		);

	}

	public float getScaleFactor() {
		return scaleFactor;
	}
	
	public void setScaleFactor(float sf) {
		this.scaleFactor = sf;
	}
}
